From ca32b4e7e7f59b472ba38b3953d09b9d379ef0ce Mon Sep 17 00:00:00 2001 From: robertlipe Date: Wed, 11 Sep 2013 05:06:34 +0000 Subject: [PATCH] Pull out a little more char* from our core infrastructure. Add shims to turn down case_ignore_strmp and case_ignore_strncmp(). Tweak reference files to deal with more correct(?) ordering in edge cases. Start sketching a shim layer for shortname, description, and text, but increasingly I'm of the opinion that our only options are either do it all in one submit (eeek!) or to add additional members of struct waypt that are allocated/copied at waypt_add time so we can then at least separate readers and writers. Instinct tells me the latter will result in harsh punishment as we'll have members that are out of sync and it will be difficult to flush them out. So substantial parts of this CL may get tossed. git-svn-id: http://gpsbabel.googlecode.com/svn/trunk@4601 f51c46e8-681c-474f-0cfe-069cfd0219fb --- gpsbabel/defs.h | 46 ++++++++++++++++++++++++--- gpsbabel/garmin_txt.cc | 2 +- gpsbabel/jeeps/gpsmath.cc | 5 +++ gpsbabel/ozi.cc | 28 ++++++++-------- gpsbabel/reference/garmin_txt-uni.csv | 4 +-- gpsbabel/reference/garmin_txt.txt | 2 +- gpsbabel/route.cc | 6 ++++ gpsbabel/util.cc | 30 ----------------- gpsbabel/waypt.cc | 12 ++++--- gpsbabel/wfff_xml.cc | 8 +++-- gpsbabel/xol.cc | 2 +- 11 files changed, 83 insertions(+), 62 deletions(-) diff --git a/gpsbabel/defs.h b/gpsbabel/defs.h index b72cf1f26..7edecc2ae 100644 --- a/gpsbabel/defs.h +++ b/gpsbabel/defs.h @@ -437,6 +437,26 @@ const global_trait* get_traits(); * be truncated, edited, or otherwise trimmed should be done on the * way to the target. */ +#if NEW_STRINGS +class String { + public: + String() : + s_(NULL) {} + bool isEmpty() { + return s_ && *s_; + } + operator char*() const { + return s_; + } + char* operator=(char* s) { + s_ = s; + return s_; + } + char* s_; +}; +#else +typedef char* String; +#endif class waypoint { @@ -447,9 +467,11 @@ public: altitude(-99999999.0), depth(0), proximity(0), +#if !NEW_STRINGS shortname(NULL), description(NULL), notes(NULL), +#endif route_priority(0), hdop(0), vdop(0), @@ -496,20 +518,20 @@ public: * minimum length for shortname is 6 characters for NMEA units, * 8 for Magellan and 10 for Vista. These are only guidelines. */ - char* shortname; + String shortname; /* * description is typically a human readable description of the * waypoint. It may be used as a comment field in some receivers. * These are probably under 40 bytes, but that's only a guideline. */ - char* description; + String description; /* * notes are relatively long - over 100 characters - prose associated * with the above. Unlike shortname and description, these are never * used to compute anything else and are strictly "passed through". * Few formats support this. */ - char* notes; + String notes; /* TODO: UrlLink should probably move to a "real" class of its own. */ @@ -963,8 +985,18 @@ void debug_mem_close(); FILE* xfopen(const char* fname, const char* type, const char* errtxt); -int case_ignore_strcmp(const char* s1, const char* s2); -int case_ignore_strncmp(const char* s1, const char* s2, int n); +// FIXME: case_ignore_strcmp() and case_ignore_strncmp() should probably +// just be replaced at the call sites. These shims are just here to make +// them more accomidating of QString input. +inline int +case_ignore_strcmp(const QString& s1, const QString& s2) { + return QString::compare(s1, s2, Qt::CaseInsensitive); +} +// In 95% of the callers, this could be s1.startsWith(s2)... +inline int case_ignore_strncmp(const QString& s1, const QString& s2, int n) { + return s1.left(n).compare(s2, Qt::CaseInsensitive); +} + int str_match(const char* str, const char* match); int case_ignore_str_match(const char* str, const char* match); char* strenquote(const char* str, const char quot_char); @@ -1173,4 +1205,8 @@ int color_to_bbggrr(const char* cname); #define unknown_alt -99999999.0 #define unknown_color -1 +// TODO: this is a (probably temporary) shim for the C->QString conversion. +// It's here instead of gps to avoid C/C++ linkage issues. +int32_t GPS_Lookup_Datum_Index(const QString& n); + #endif /* gpsbabel_defs_h_included */ diff --git a/gpsbabel/garmin_txt.cc b/gpsbabel/garmin_txt.cc index 60dc628a2..5120c2a76 100644 --- a/gpsbabel/garmin_txt.cc +++ b/gpsbabel/garmin_txt.cc @@ -227,7 +227,7 @@ sort_waypt_cb(const void* a, const void* b) const waypoint* wa = *(waypoint**)a; const waypoint* wb = *(waypoint**)b; - return case_ignore_strcmp(wa->shortname, wb->shortname); + return case_ignore_strcmp(QString::fromLatin1(wa->shortname), QString::fromLatin1(wb->shortname)); } diff --git a/gpsbabel/jeeps/gpsmath.cc b/gpsbabel/jeeps/gpsmath.cc index a5e9de25d..ecb34c74d 100644 --- a/gpsbabel/jeeps/gpsmath.cc +++ b/gpsbabel/jeeps/gpsmath.cc @@ -2572,6 +2572,11 @@ int32 GPS_Lookup_Datum_Index(const char* n) return -1; } +int32 GPS_Lookup_Datum_Index(const QString& n) +{ + return GPS_Lookup_Datum_Index(CSTR(n)); +} + const char* GPS_Math_Get_Datum_Name(const int datum_index) { diff --git a/gpsbabel/ozi.cc b/gpsbabel/ozi.cc index 736027867..2adc9ec3f 100644 --- a/gpsbabel/ozi.cc +++ b/gpsbabel/ozi.cc @@ -720,15 +720,14 @@ ozi_parse_routeheader(int field, char* str, waypoint* wpt_tmp) static void data_read(void) { - char* buff; + QString buff; char* s = NULL; char* trk_name = NULL; waypoint* wpt_tmp; int i; int linecount = 0; - while ((buff = gbfgetstr(file_in))) { - + while ((buff = gbfgetstr(file_in)), !buff.isNull()) { if ((linecount++ == 0) && file_in->unicode) { cet_convert_init(CET_CHARSET_UTF8, 1); } @@ -738,36 +737,37 @@ data_read(void) * to attempt to divine the data type we are parsing */ if (linecount == 1) { - if (strstr(buff, "Track Point") != NULL) { + if (buff.contains("Track Point")) { trk_head = route_head_alloc(); track_add_head(trk_head); ozi_objective = trkdata; - } else if (strstr(buff, "Route File") != NULL) { + } else if (buff.contains("Route File")) { ozi_objective = rtedata; } else { ozi_objective = wptdata; } } else if (linecount == 2) { datum = GPS_Lookup_Datum_Index(buff); + if (datum < 0) { - fatal(MYNAME ": Unsupported datum '%s'.\n", buff); + fatal(MYNAME ": Unsupported datum '%s'.\n", CSTR(buff)); } } else if (linecount == 3) { - if (case_ignore_strncmp(buff, "Altitude is in ", 15) == 0) { - char* unit = &buff[15]; - if (case_ignore_strncmp(unit, "Feet", 4) == 0) { + if (buff.startsWith( "Altitude is in ", Qt::CaseInsensitive)) { + QString unit = buff.mid(15); + if (unit.startsWith("Feet", Qt::CaseInsensitive)) { altunit = 'f'; alt_scale = FEET_TO_METERS(1.0); - } else if (case_ignore_strncmp(unit, "Meter", 5) == 0) { + } else if (unit.startsWith("Meter", Qt::CaseInsensitive)) { altunit = 'm'; alt_scale = 1.0; } else { - fatal(MYNAME ": Unknown unit (%s) used by altitude values!\n", unit); + fatal(MYNAME ": Unknown unit (%s) used by altitude values!\n", CSTR(unit)); } } } else if ((linecount == 5) && (ozi_objective == trkdata)) { int field = 0; - s = csv_lineparse(buff, ",", "", linecount); + s = csv_lineparse(CSTR(buff), ",", "", linecount); while (s) { field ++; if (field == 4) { @@ -777,13 +777,13 @@ data_read(void) } } - if ((strlen(buff)) && (strstr(buff, ",") != NULL)) { + if (buff.contains(',')) { bool ozi_fsdata_used = false; ozi_fsdata* fsdata = ozi_alloc_fsdata(); wpt_tmp = waypt_new(); /* data delimited by commas, possibly enclosed in quotes. */ - s = buff; + s = xstrdup(CSTR(buff)); s = csv_lineparse(s, ",", "", linecount); i = 0; diff --git a/gpsbabel/reference/garmin_txt-uni.csv b/gpsbabel/reference/garmin_txt-uni.csv index 51ba3799b..9fa7aea5b 100644 --- a/gpsbabel/reference/garmin_txt-uni.csv +++ b/gpsbabel/reference/garmin_txt-uni.csv @@ -10,6 +10,6 @@ No,Latitude,Longitude,Name,Altitude,Description,Symbol,Date,Time,URL,Facility,Ci 9,38.631995,-3.174055,"GC_X",,"Dummy airport (Spain)","Airport",2006/03/28,01:42:01,,"FAC2","CITY2","Canary Island" 10,50.493667,12.107150,"Jahnstrasse",,"Jahnstrasse 11","Flag, Red",2006/03/31,21:48:22,,,, 11,46.387606,3.498277,"LF_X",,"Dummy airport (France)","Airport",2006/03/28,01:40:32,,"FAC3","CITY3","France" -12,50.493834,12.106100,"Liebknechtstrasse",,"Liebknechtstrasse 90","Waypoint",2006/03/31,21:49:30,,,, -13,43.314550,12.161554,"LI_X",,"Dummy airport (Italy)","Heliport",2006/03/28,01:43:25,,"FAC4","CITY4","Italy" +12,43.314550,12.161554,"LI_X",,"Dummy airport (Italy)","Heliport",2006/03/28,01:43:25,,"FAC4","CITY4","Italy" +13,50.493834,12.106100,"Liebknechtstrasse",,"Liebknechtstrasse 90","Waypoint",2006/03/31,21:49:30,,,, 14,50.492616,12.105448,"NARVA",391.0,"Start","Flag, Green",2006/03/31,21:49:26,"http://www.narva-light.de",,, diff --git a/gpsbabel/reference/garmin_txt.txt b/gpsbabel/reference/garmin_txt.txt index dae88c25b..e11091ffe 100644 --- a/gpsbabel/reference/garmin_txt.txt +++ b/gpsbabel/reference/garmin_txt.txt @@ -14,8 +14,8 @@ Waypoint ED_X Dummy airport (Germany) Airport N51 53.627961650 E12 58.676564991 Waypoint GC_X Dummy airport (Spain) Airport N38 37.919719778 W3 10.443304181 Symbol & Name Unknown Airport FAC2 CITY2 Canary Island 28/03/2006 01:42:01 Waypoint Jahnstrasse Jahnstrasse 11 User Waypoint N50 29.619998485 E12 06.429000869 Symbol & Description Unknown Flag, Red 31/03/2006 21:48:22 Waypoint LF_X Dummy airport (France) Airport N46 23.256332763 E3 29.896638617 Symbol & Name Unknown Airport FAC3 CITY3 France 28/03/2006 01:40:32 -Waypoint Liebknechtstrasse Liebknechtstrasse 90 User Waypoint N50 29.630041681 E12 06.366015896 Symbol & Name Unknown Waypoint 31/03/2006 21:49:30 Waypoint LI_X Dummy airport (Italy) Airport N43 18.873018846 E12 09.693240859 Symbol & Name Unknown Heliport FAC4 CITY4 Italy 28/03/2006 01:43:25 +Waypoint Liebknechtstrasse Liebknechtstrasse 90 User Waypoint N50 29.630041681 E12 06.366015896 Symbol & Name Unknown Waypoint 31/03/2006 21:49:30 Waypoint NARVA Start User Waypoint N50 29.556958191 E12 06.326884143 391 m Symbol Unknown Flag, Green 31/03/2006 21:49:26 http://www.narva-light.de Category 15 diff --git a/gpsbabel/route.cc b/gpsbabel/route.cc index 2abce768c..aa23f5efd 100644 --- a/gpsbabel/route.cc +++ b/gpsbabel/route.cc @@ -180,7 +180,13 @@ any_route_add_wpt(route_head* rte, waypoint* wpt, int* ct, int synth, const char (*ct)++; } if (synth && !wpt->shortname) { +#if NEW_STRINGS + char *t; + xasprintf(&t, "%s%0*d", namepart, number_digits, *ct); + wpt->shortname = t; +#else xasprintf(&wpt->shortname,"%s%0*d", namepart, number_digits, *ct); +#endif wpt->wpt_flags.shortname_is_synthetic = 1; } update_common_traits(wpt); diff --git a/gpsbabel/util.cc b/gpsbabel/util.cc index 581a8704e..34dce8d12 100644 --- a/gpsbabel/util.cc +++ b/gpsbabel/util.cc @@ -420,36 +420,6 @@ lrtrim(char* buff) return buff; } -/* - * Like strcmp, but case insensitive. Like Berkeley's strcasecmp. - */ - -int -case_ignore_strcmp(const char* s1, const char* s2) -{ - for (; toupper(*s1) == toupper(*s2); ++ s1, ++s2) { - if (*s1 == 0) { - return 0; - } - } - return (toupper(*s1) < toupper(*s2)) ? -1 : +1; - -} - -int -case_ignore_strncmp(const char* s1, const char* s2, int n) -{ - int rv = 0; - - while (n && ((rv = toupper(*s1) - toupper(*s2)) == 0) - && *s1) { - s1++; - s2++; - n--; - } - return rv; -} - /* * compare str with match * match may contain wildcards "*" and "?" diff --git a/gpsbabel/waypt.cc b/gpsbabel/waypt.cc index e69cffc7a..582c29928 100644 --- a/gpsbabel/waypt.cc +++ b/gpsbabel/waypt.cc @@ -160,12 +160,12 @@ waypt_add(waypoint* wpt) } if ((wpt->latitude < -90) || (wpt->latitude > 90.0)) - fatal("%s: Invalid latitude %f in waypoint %s.\n", + fatal("%s: Invalid latitude %f in waypoint '%s'.\n", wpt->session->name, - lat_orig, wpt->shortname ? wpt->shortname : ""); + lat_orig, wpt->shortname); if ((wpt->longitude < -180) || (wpt->longitude > 180.0)) - fatal("Invalid longitude %f in waypoint %s.\n", - lon_orig, wpt->shortname ? wpt->shortname : ""); + fatal("Invalid longitude %f in waypoint '%s'.\n", + lon_orig, wpt->shortname); /* * Some input may not have one or more of these types so we @@ -179,7 +179,9 @@ waypt_add(waypoint* wpt) wpt->shortname = xstrdup(wpt->notes); } else { /* Last ditch: make up a name */ - xasprintf(&wpt->shortname, "WPT%03d", waypt_ct); + char *sn; + xasprintf(&sn, "WPT%03d", waypt_ct); + wpt->shortname = sn; } } diff --git a/gpsbabel/wfff_xml.cc b/gpsbabel/wfff_xml.cc index 65be3a8f5..4e57e5c81 100644 --- a/gpsbabel/wfff_xml.cc +++ b/gpsbabel/wfff_xml.cc @@ -227,14 +227,16 @@ void wfff_e(const char* args, const QXmlStreamAttributes* unused) wpt_tmp->altitude = unknown_alt; wpt_tmp->fix = fix_unknown; - if (case_ignore_strncmp(ap_wep,"On",2)==0) { - if (case_ignore_strncmp(ap_type,"AP",2)==0) { + QString ap_wep_(ap_wep); + QString ap_type_(ap_type); + if (ap_wep_.startsWith("on", Qt::CaseInsensitive)) { + if (ap_type_.startsWith("AP", Qt::CaseInsensitive)) { wpt_tmp->icon_descr = aicicon; /* Infra Closed */ } else { wpt_tmp->icon_descr = ahcicon; /* AdHoc Closed */ } } else { - if (case_ignore_strncmp(ap_type,"AP",2)==0) { + if (ap_type_.startsWith("AP", Qt::CaseInsensitive)) { wpt_tmp->icon_descr = aioicon; /* Infra Open */ } else { wpt_tmp->icon_descr = ahoicon; /* AdHoc Open */ diff --git a/gpsbabel/xol.cc b/gpsbabel/xol.cc index de290024c..32169c17e 100644 --- a/gpsbabel/xol.cc +++ b/gpsbabel/xol.cc @@ -227,7 +227,7 @@ static void xol_waypt_disp_cb(const waypoint* wpt) { double x, y; - char* name; + const char* name; name = wpt->shortname; if ((name == NULL) || (*name == '\0') || global_opts.synthesize_shortnames) { -- 2.30.2